home *** CD-ROM | disk | FTP | other *** search
/ Amiga Plus Leser 15 / Amiga Plus Leser CD 15.iso / Tools / Development / MosaicSRC / libwww2 / HTMail.c < prev    next >
Encoding:
C/C++ Source or Header  |  2002-03-13  |  6.7 KB  |  446 lines

  1. /*
  2. **  HTMail.c
  3. */
  4.  
  5. #include <proto/dos.h>
  6. #include <proto/exec.h>
  7.  
  8. #include <dos/dostags.h>
  9.  
  10. #include <string.h>
  11. #include <stdio.h>
  12. #include <stdlib.h>
  13.  
  14. #include "HTAccess.h"
  15. #include "HTAnchor.h"
  16. #include "HTUtils.h"
  17.  
  18. LONG StatFile (const UBYTE *, struct FileInfoBlock *);
  19. BPTR OpenTemp (UBYTE *);
  20. LONG Compose (const char *, const char *);
  21.  
  22. extern void application_user_feedback (char *);
  23. extern char *amiga_editor;
  24. extern char *amiga_sendmail;
  25.  
  26. static char
  27.     buf [256];
  28.  
  29. LONG
  30. StatFile (const UBYTE *filename, struct FileInfoBlock *fib)
  31. {
  32.     BPTR
  33.         lock = Lock ((UBYTE *) filename, ACCESS_READ);
  34.     LONG
  35.         i = 0;
  36.  
  37.     if (!lock)
  38.     {
  39.         i = -1;
  40.     }
  41.     else
  42.     {
  43.         if (!Examine (lock, fib))
  44.             i = -1;
  45.     }
  46.  
  47.     if (lock)
  48.     {
  49.         UnLock (lock);
  50.     }
  51.  
  52.     if (i < 0)
  53.     {
  54.         sprintf (buf, "Can't open %s", filename);
  55.         application_user_feedback (buf);
  56.     }
  57.  
  58.     return i;
  59. }
  60.  
  61. static LONG
  62. Editor (const UBYTE *filename)
  63. {
  64.     /*
  65.     **  Editor
  66.     **
  67.     **    Call the specified editor to edit the specified filename.
  68.     **
  69.     **    If the Editor failed (non-zero return value), or the user
  70.     **    did not modify the input file, then let the user know, and
  71.     **    return an appropriate value to the caller.
  72.     */
  73.     LONG
  74.         erslt,
  75.         rslt = 1;
  76.     UBYTE
  77.         *buf = malloc (256);
  78.     struct FileInfoBlock
  79.         *fib1 = NULL,
  80.         *fib2 = NULL;
  81.  
  82.     if (!buf)
  83.     {
  84.         goto leave;
  85.     }
  86.  
  87.     fib1 = AllocDosObject (DOS_FIB, NULL);
  88.     if (!fib1)
  89.     {
  90.         goto leave;
  91.     }
  92.  
  93.     fib2 = AllocDosObject (DOS_FIB, NULL);
  94.     if (!fib2)
  95.     {
  96.         goto leave;
  97.     }
  98.  
  99.     if (StatFile (filename, fib1) < 0)
  100.     {
  101.         goto leave;
  102.     }
  103.  
  104.     sprintf (buf, "%s %s", amiga_editor, filename);
  105.  
  106.     erslt = SystemTags (buf,
  107.             SYS_UserShell, 1,
  108.             NP_StackSize,  32000,
  109.             TAG_DONE);
  110.  
  111.     if (erslt == -1)
  112.     {
  113.         sprintf (buf, "Couldn't start editor %s", amiga_editor);
  114.         application_user_feedback (buf);
  115.         goto leave;
  116.     }
  117.  
  118.     if (erslt)
  119.     {
  120.         sprintf (buf, "Editor returned error %ld\nMessage discarded", erslt);
  121.         application_user_feedback (buf);
  122.         goto leave;
  123.     }
  124.  
  125.     StatFile (filename, fib2);
  126.  
  127.     if (CompareDates (&fib1->fib_Date, &fib2->fib_Date) == 0)
  128.     {
  129.         application_user_feedback ("No changes to input file.\nMessage discarded");
  130.         goto leave;
  131.     }
  132.  
  133.     /*
  134.     ** everything worked OK
  135.     */
  136.     rslt = 0;
  137.  
  138. leave:
  139.     if (fib2)
  140.     {
  141.         FreeDosObject (DOS_FIB, fib2);
  142.     }
  143.  
  144.     if (fib1)
  145.     {
  146.         FreeDosObject (DOS_FIB, fib1);
  147.     }
  148.  
  149.     if (buf)
  150.     {
  151.         free (buf);
  152.     }
  153.  
  154.     return rslt;
  155. }
  156.  
  157. static LONG
  158. SendMail (const int edit, const UBYTE *filename)
  159. {
  160.     /*
  161.     **  SendMail
  162.     **
  163.     **    Take a completely built article in 'filename' and go through
  164.     **    the required steps to inject the message into the mail system.
  165.     **
  166.     **    Returns zero if the mail was sent correctly.
  167.     **
  168.     **    This routine will ensure that filename is deleted.
  169.     */
  170.     LONG
  171.         rslt = 1,   /* assume failure */
  172.         len = strlen (filename) + 1;
  173.     UBYTE
  174.         *buf   = malloc (256),
  175.         *fname = malloc (len);
  176.     BPTR
  177.         inp = NULL;
  178.  
  179.     if (!buf)
  180.     {
  181.         goto leave;
  182.     }
  183.     if (!fname)
  184.     {
  185.         goto leave;
  186.     }
  187.  
  188.     /* save filename -- it may be from TempName() */
  189.     strcpy (fname, filename);
  190.  
  191.     if (edit && Editor (fname))
  192.     {
  193.         goto leave;
  194.     }
  195.  
  196.     inp = Open ("NIL:", MODE_NEWFILE);
  197.     if (!inp)
  198.     {
  199.         application_user_feedback ("Can't open NIL:");
  200.         goto leave;
  201.     }
  202.  
  203.     sprintf (buf, "%s <%s\ndelete >nil: quiet %s\n", amiga_sendmail, fname, fname);
  204.  
  205.     rslt = SystemTags (buf,
  206.             SYS_Input,     inp,
  207.             SYS_Output,    0,
  208.             SYS_Asynch,    1,
  209.             SYS_UserShell, 1,
  210.             NP_StackSize,  32000,
  211.             TAG_DONE);
  212.  
  213.     if (rslt != -1)
  214.     {
  215.         inp = 0;
  216.         rslt = 0;
  217.     }
  218.  
  219.     if (rslt != 0)
  220.     {
  221.         if (rslt < 0)
  222.             sprintf (buf, "Could not initiate %s", amiga_sendmail);
  223.         else
  224.             sprintf (buf, "Error from %s\nReturn value %ld", amiga_sendmail, rslt);
  225.         application_user_feedback (buf);
  226.     }
  227.  
  228. leave:
  229.     if (inp)
  230.     {
  231.         Close (inp);
  232.     }
  233.  
  234.     if (fname)
  235.     {
  236.         free (fname);
  237.     }
  238.  
  239.     if (buf)
  240.     {
  241.         free (buf);
  242.     }
  243.  
  244.     return rslt;
  245. }
  246.  
  247. static void
  248. AppendHeader (BPTR file)
  249. {
  250.     BPTR
  251.         header;
  252.     APTR
  253.         winptr;
  254.     struct Process
  255.         *me = (struct Process *) FindTask (NULL);
  256.     UBYTE
  257.         *buf = malloc (256);
  258.  
  259.     const UBYTE
  260.         H_Name [] = "uulib:.header";
  261.  
  262.     extern char
  263.         *amosaic_version;
  264.  
  265.     if (!buf)
  266.     {
  267.         return;
  268.     }
  269.  
  270.     winptr = me->pr_WindowPtr;
  271.     me->pr_WindowPtr = (APTR) -1;
  272.  
  273.     if (header = Open ((UBYTE *) H_Name, MODE_OLDFILE))
  274.     {
  275.         while (FGets (header, buf, 254))
  276.         {
  277.             Write (file, buf, strlen (buf));
  278.         }
  279.         Close (header);
  280.     }
  281.  
  282.     sprintf (buf, "X-Mailer: %s\n\n", &amosaic_version [6]);
  283.     Write (file, buf, strlen (buf));
  284.  
  285.     free (buf);
  286.     me->pr_WindowPtr = winptr;
  287.  
  288.     return;
  289. }
  290.  
  291. static void
  292. AppendSignature (BPTR file)
  293. {
  294.     BPTR
  295.         sig;
  296.     UBYTE
  297.         *buf = malloc (256);
  298.     APTR
  299.         winptr;
  300.     struct Process
  301.         *me = (struct Process *) FindTask (NULL);
  302.  
  303.     const UBYTE
  304.         S_Name [] = "uulib:.signature";
  305.  
  306.     if (!buf)
  307.     {
  308.         return;
  309.     }
  310.  
  311.     winptr = me->pr_WindowPtr;
  312.     me->pr_WindowPtr = (APTR) -1;
  313.  
  314.     if (sig = Open ((UBYTE *) S_Name, MODE_OLDFILE))
  315.     {
  316.         Write (file, "-- \n", 4);
  317.         while (FGets (sig, buf, 254))
  318.         {
  319.             Write (file, buf, strlen (buf));
  320.         }
  321.         Close (sig);
  322.     }
  323.  
  324.     free (buf);
  325.     me->pr_WindowPtr = winptr;
  326.  
  327.     return;
  328. }
  329.  
  330. static const UBYTE
  331.     HEADER_Start [] = "To: %s\nSubject: %s%s\n";
  332. static long
  333.     temp_inx = 1;
  334.  
  335. BPTR
  336. OpenTemp (UBYTE *ptr)
  337. {
  338.     BPTR
  339.         t;
  340.  
  341.     sprintf (ptr, "T:T.%lx.%ld.mosaic", FindTask (NULL), temp_inx++);
  342.     t = Open (ptr, MODE_NEWFILE);
  343.     if (!t)
  344.     {
  345.         sprintf (buf, "Can't open %s", ptr);
  346.         application_user_feedback (buf);
  347.     }
  348.  
  349.     return t;
  350. }
  351.  
  352. LONG
  353. Compose (const char *where, const char *orig_url)
  354. {
  355.     UBYTE
  356.         *ptr = malloc (256);
  357.     BPTR
  358.         mail;
  359.     LONG
  360.         rslt;
  361.  
  362.     if (!ptr)
  363.     {
  364.         return HT_NOT_LOADED;
  365.     }
  366.  
  367.     mail = OpenTemp (ptr);
  368.     if (!mail)
  369.     {
  370.         goto leave;
  371.     }
  372.  
  373.     sprintf (buf, HEADER_Start, where ? where : "", orig_url ? orig_url : "", "");
  374.     Write (mail, buf, strlen (buf));
  375.     AppendHeader (mail);
  376.     AppendSignature (mail);
  377.     Close (mail);
  378.  
  379.     rslt = SendMail (1, ptr);
  380.  
  381.     if (rslt)
  382.         rslt = HT_NOT_LOADED;
  383.     else
  384.         rslt = HT_LOADED;  /* success, but no document */
  385.  
  386. leave:
  387.     if (ptr)
  388.     {
  389.         free (ptr);
  390.     }
  391.  
  392.     return rslt;
  393. }
  394.  
  395. static int mailinitialized;
  396.  
  397. static int mailinitialize (void)
  398. {
  399.     if (!amiga_editor || *amiga_editor == '\0')
  400.     {
  401.         application_user_feedback ("Mosaic/Editor is not defined");
  402.         return 0;
  403.     }
  404.  
  405.     if (!amiga_sendmail || *amiga_sendmail == '\0')
  406.     {
  407.         application_user_feedback ("Mosaic/Sendmail is not defined");
  408.         return 0;
  409.     }
  410.  
  411.     mailinitialized = 1;
  412.     return 1;
  413. }
  414.  
  415. int
  416. HTLoadMail (const char * arg, HTParentAnchor * anchor, HTFormat format_out, HTStream * stream)
  417. {
  418.     const char
  419.         *ptr;
  420.     int
  421.         rslt;
  422.  
  423.     CTRACE (stderr, "HTLoadMail: arg '%s', address '%s' physical '%s' title '%s'\n", arg, anchor->address, anchor->physical, anchor->title);
  424.     CTRACE (stderr, "parent is self == %s\n", anchor->parent == anchor ? "true" : "false");
  425.  
  426.     if (!mailinitialized)
  427.     {
  428.         if (!mailinitialize ())
  429.         {
  430.             CTRACE (stderr, "HTLoadMail: mailinitialize() failed\n");
  431.             return HT_NOT_LOADED;
  432.         }
  433.     }
  434.  
  435.     ptr = arg;
  436.     if (strnicmp (ptr, "mailto:", 7) == 0)
  437.         ptr += 7;
  438.  
  439.     rslt = (int) Compose (ptr, anchor->address);
  440.     CTRACE (stderr, "Compose() returned %ld\n", rslt);
  441.  
  442.     return rslt;
  443. }
  444.  
  445. HTProtocol HTMail = { "mailto", HTLoadMail, NULL };
  446.